package com.gm.wj.service;

import com.gm.wj.config.RedisConfig;
import com.gm.wj.dao.SysNewsDAO;
import com.gm.wj.entity.JotterArticle;
import com.gm.wj.entity.SysNews;
import com.gm.wj.redis.RedisService;
import com.gm.wj.util.MyPage;
import lombok.extern.slf4j.Slf4j;
import org.apache.shiro.SecurityUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Pageable;
import org.springframework.data.jpa.domain.Specification;
import org.springframework.stereotype.Service;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.PageRequest;
import org.springframework.data.domain.Sort;

import javax.persistence.criteria.Predicate;
import java.util.ArrayList;
import java.util.List;
import java.util.Set;

/**
 * @program: wj
 * @description: 最近更新
 * @author: Huang_shengjun
 * @create: 2020-12-10 17:23
 **/
@Slf4j
@Service
public class SysNewsService {
    @Autowired
    SysNewsDAO sysNewsDAO;
    @Autowired
    RedisService redisService;
    @Autowired
    PermissionURL permissionURL;

    public SysNews findById(int id) {
        SysNews sysNews;
        String key = "sysNews:" + id;
        Object sysNewsCache = redisService.get(key);

        if (sysNewsCache == null) {
            sysNews = sysNewsDAO.findById(id);
            redisService.set(key, sysNews,RedisConfig.DATA_REDIS_KEY_TIME);
        } else {
            sysNews = (SysNews) sysNewsCache;
        }
        return sysNews;
    }

    public int addOrUpdate(SysNews sysNews) {
        String username = (String) SecurityUtils.getSubject().getPrincipal();
        sysNews.setUsername(username);
        sysNewsDAO.save(sysNews);
        redisService.delete("sysNews" + sysNews.getId());
        Set<String> keys = redisService.getKeysByPattern("sysNewspage*");
        redisService.delete(keys);
        return 1;
    }

    public void delete(int id) {
        sysNewsDAO.deleteById(id);
        redisService.delete("sysNews:" + id);
        Set<String> keys = redisService.getKeysByPattern("sysNewspage*");
        redisService.delete(keys);
    }

    public MyPage listIndex(int page, int size) {
        MyPage<SysNews> sysNews;
        // list缓存
        String key = "sysNewspage:" + page;
        Object sysNewsPageCache = redisService.get(key);

        // 如果为空，就再查询一次，写入redis缓存
        if (sysNewsPageCache == null) {
            Sort sort = Sort.by(Sort.Direction.DESC, "createTime");
            Page<SysNews> bannerInDb = sysNewsDAO.findAll(PageRequest.of(page, size, sort));
            sysNews = new MyPage<>(bannerInDb);
            // 设置redis过期时间  5s
            redisService.set(key, sysNews, RedisConfig.DATA_REDIS_KEY_TIME);
        } else {
            sysNews = (MyPage<SysNews>) sysNewsPageCache;
        }
        return sysNews;
    }

    public MyPage list(int page, int size, String queryKey1) {
        // 获取操作用户名
        String username = (String) SecurityUtils.getSubject().getPrincipal();
        MyPage<SysNews> sysNews;
        // list缓存
        String key =  username + "sysNewspage:" + page;
        Object sysNewsPageCache = redisService.get(key);

        // 如果为空，就再查询一次，写入redis缓存
        if (sysNewsPageCache == null) {
            Sort sort = Sort.by(Sort.Direction.DESC, "id");
            Pageable pageable = new PageRequest(page, size,sort);

            // 重写 findAll方法  多条件查询
            Page<SysNews> sysNewsInDb = sysNewsDAO.findAll((Specification<SysNews>) (root, criteriaQuery, criteriaBuilder) -> {
                List<javax.persistence.criteria.Predicate> list = new ArrayList<javax.persistence.criteria.Predicate>();
                // 实体类字段，不是数据库字段
                list.add(criteriaBuilder.equal(root.get("username").as(String.class), username));
                // 如果拥有权限  清除只能查询自己的数据的条件查询
                if(permissionURL.isPermissionURL(JotterArticle.class.getSimpleName(),username)){
                    list.removeAll(list);
                }
                if(!"".equals(queryKey1)&&null!=queryKey1){
                    log.info("进入newContent语句2" + queryKey1);
                    list.add(criteriaBuilder.like(root.get("newContent").as(String.class), "%" + queryKey1 + "%"));
                }
                javax.persistence.criteria.Predicate[] p = new Predicate[list.size()];
                return criteriaBuilder.and(list.toArray(p));
            },pageable);

            sysNews = new MyPage<>(sysNewsInDb);
            // 设置redis过期时间  5s
            redisService.set(key, sysNews,RedisConfig.DATA_REDIS_KEY_TIME);
        } else {
            sysNews = (MyPage<SysNews>) sysNewsPageCache;
        }
        return sysNews;
    }

}
